<?php
function collect_attributes($class_id, $excluded_attr){
  global $language;
  // this functional coolects attributes of this class and all inherited attributes for this class
  if ($class_id == "")
    die("Functional.php: collect_attributes: class_id is empty.");
  $attrs = Array();
  $result = getMultdata("SELECT c.attr_id, t.text FROM class_attr c, attr a, term t WHERE c.class_id = ".$class_id." and a.id = c.attr_id and a.term_id = t.id and a.id <> ".$excluded_attr." and t.lang_id = ".$language["content"], $attrs);
  $i = count($attrs);
  $class_data["class_id"] = $class_id;
  while ($class_data["class_id"] > 0){
    getdata("SELECT parent_id as class_id FROM class WHERE id = ".$class_data["class_id"], $class_data);
    $result = getMultdata("SELECT c.attr_id, t.text FROM class_attr c, attr a, term t WHERE c.class_id = ".$class_data["class_id"]." and a.id = c.attr_id and a.term_id = t.id and a.id <> ".$excluded_attr." and t.lang_id = ".$language["content"], $attrs_temp);
    for ($j = 0; $j < $result; $j++){
      $attrs[$i]["attr_id"] = $attrs_temp[$j]["attr_id"];
      $attrs[$i]["text"] = $attrs_temp[$j]["text"];
      $i++;
    };
  };
  return $attrs;
};

function functionalListFolderData($mes) {
  global $_GET, $path, $style, $session_id, $data, $term_Thing_ID, $language, $header;
  $filename = $path[$style]["tpl"]."/attrdata.xml";
  $fp = fopen($filename, "r");
  $contents = fread($fp, filesize ($filename));
  fclose ($fp);

  preg_match("/\%REPEAT\%(.*?)\%REPEAT\%/s", $contents, $matches);
  preg_match("/\%REPDAT\%(.*?)\%REPDAT\%/s", $matches[1], $datmatches);

  $udata = str_replace($datmatches[0], "", $matches[1]);
  $udata = str_replace("%GROUP_ID%", "0", $udata);
  $udata = str_replace("%GROUP_TL%", $mes, $udata);
  $contents = str_replace("%DatHref%", "index.php?trg=ontoedit&amp;act=functionallistdata&amp;sid=".
              $session_id."&amp;uid=".$_GET["uid"], $contents);

  header ($header["xml"]);
  return str_replace($matches[0], $udata, $contents);
}

function getFunctional($class_id, $matches, $session_id, $element){
  global $_GET, $undef_id, $language;
  $fun_id = substr($_GET["uid"], 0, 4);
  $next_class_id = $class_id;
  $class1_id = $next_class_id;
  $sql_str = "SELECT t.text FROM class c, term t WHERE t.id=c.term_id and c.id=".$class_id;
  getData($sql_str, $next_data);
  $inherited = false;
  $rep_cont = "";

  while ($next_data["text"] != "Thing"){
    switch ($element) {
      case "class":
        $sql_str = "SELECT f.id, t.text, f.func_value FROM func_constr f, term t WHERE f.term_id = t.id and t.lang_id = ".$language["content"]." and relation_type = 0 and f.Relation_id = ".$next_class_id;
        $sql_str_reverce = "SELECT f.id, t.text, f.func_value FROM func_constr f, term t WHERE f.term_id = t.id and t.lang_id = ".$language["content"]." and relation_type = 0 and f.func_type = 0 and f.func_value = ".$next_class_id;
        break;
      case "hierarchy":
        $childclass = substr($_GET["uid"], strrpos($_GET["uid"], "h") + 1);
        $sql_str = "SELECT f.id, t.text, f.func_value FROM func_constr f, term t WHERE f.term_id = t.id and t.lang_id = ".$language["content"]." and relation_type = 1 and f.Relation_id = (SELECT id FROM hierarchy WHERE parent_class_id = ".$next_class_id." and child_class_id =".$childclass.")";
        $sql_str_reverce = "SELECT f.id, t.text, f.func_value FROM func_constr f, term t WHERE f.term_id = t.id and t.lang_id = ".$language["content"]." and relation_type = 1 and f.func_type = 0 and f.func_value = ".$next_class_id;
        break;
      case "acon":
        $childclass = substr($_GET["uid"], strrpos($_GET["uid"], "ac") + 2);
        $sql_str = "SELECT f.id, t.text, f.func_value FROM func_constr f, term t WHERE f.term_id = t.id and t.lang_id = ".$language["content"]." and relation_type = 2 and f.Relation_id = (SELECT id FROM acon WHERE class1_id = ".$next_class_id." and class2_id = ".$childclass.")";
        $sql_str_reverce = "SELECT f.id, t.text, f.func_value FROM func_constr f, term t WHERE f.term_id = t.id and t.lang_id = ".$language["content"]." and relation_type = 2 and f.func_type = 0 and f.func_value = ".$next_class_id;
        break;
    }
    $i_max = getMultData($sql_str, $ontosdata);

    for ($i = 0; $i < $i_max; $i++) {
      $tmp_attr = str_replace("%CLASS_ID%", $fun_id.$ontosdata[$i]["id"], $matches[1]);
      if (isset($_GET["sel"]) && $_GET["sel"] == $fun_id.$ontosdata[$i]["id"])
        $tmp_attr = str_replace("%ACT%", "select", $tmp_attr);
      $tmp_attr = str_replace("%CLASS_NM%", $ontosdata[$i]["text"], $tmp_attr);
      if ($inherited)
        $tmp_attr = str_replace("%IMG_TYPE%", "inhfunctional", $tmp_attr);
      else
        $tmp_attr = str_replace("%IMG_TYPE%", "functional", $tmp_attr);
      $tmp_attr = str_replace("%CLASS_LN%", "index.php?trg=ontoedit&amp;act=functionaldata&amp;sid=".
      $session_id."&amp;uid=".$fun_id.$ontosdata[$i]["id"], $tmp_attr);

      // determine if has child
      if (isset($ontosdata[$i]["func_value"]) /*&& count(collect_attributes($ontosdata[$i]["func_value"], 0)) > 0*/)
        $tmp_attr = str_replace("%CHILD_LN%", "index.php?trg=ontoedit&amp;act=getfunctionalattrs&amp;sid=".$session_id."&amp;uid=".$fun_id.$ontosdata[$i]["id"], $tmp_attr);
      else
        $tmp_attr = str_replace("%CHILD_LN%", "", $tmp_attr);


      if (isset($_GET["sel"]) &&
        ($_GET["sel"] == $fun_id.$ontosdata[$i]["id"] || ($_GET["sel"] == 0 && $i == 0))) {
        $tmp_attr = str_replace("%ACT%", "select", $tmp_attr);
      }
      $rep_cont .= $tmp_attr;
    };

    // reverce functional constraint
    $j_max = getMultData($sql_str_reverce, $ontosdata);
    for ($i = 0; $i < $j_max; $i++) {
      $tmp_attr = str_replace("%CLASS_ID%", $fun_id."r".$ontosdata[$i]["id"], $matches[1]);
      $tmp_attr = str_replace("%CLASS_LN%", "index.php?trg=ontoedit&amp;act=functionaldata&amp;sid=".$session_id."&amp;uid=".$fun_id."r".$ontosdata[$i]["id"], $tmp_attr);
      // determine if has child
      if (isset($ontosdata[$i]["func_value"]))
        $tmp_attr = str_replace("%CHILD_LN%", "index.php?trg=ontoedit&amp;act=getfunctionalattrs&amp;sid=".$session_id."&amp;uid=".$fun_id."r".$ontosdata[$i]["id"], $tmp_attr);
      else
        $tmp_attr = str_replace("%CHILD_LN%", "", $tmp_attr);

      if (isset($_GET["sel"]) && ($_GET["sel"] == $fun_id.$ontosdata[$i]["id"] || ($_GET["sel"] == 0 && $i == 0)))
        $tmp_attr = str_replace("%ACT%", "select", $tmp_attr);
      $tmp_attr = str_replace("%CLASS_NM%", $ontosdata[$i]["text"], $tmp_attr);
      if ($inherited)
        $tmp_attr = str_replace("%IMG_TYPE%", "inhfunctional", $tmp_attr);
      else
        $tmp_attr = str_replace("%IMG_TYPE%", "functional_reverce", $tmp_attr);

      $rep_cont .= $tmp_attr;
    };

    $sql_str = "SELECT parent_id FROM class WHERE id=".$next_class_id;
    getData($sql_str, $next_data);
    $next_class_id = $next_data["parent_id"];
    $sql_str = "SELECT t.text FROM class c, term t WHERE t.id=c.term_id and c.id=".$next_class_id;
    getData($sql_str, $next_data);
    $inherited = true;
    $fun_id .= "i";
  };
  return $rep_cont;
};

// get list of functional relations and return XML contains it
function functionalList(){
 global $_GET, $data, $path, $style, $session_id, $language, $header;
  $filename = $path[$style]["tpl"]."/classes.xml";
  $fp = fopen($filename, "r");
  $contents = fread($fp, filesize ($filename));
  fclose ($fp);

  preg_match("/\%REPEAT\%(.*?)\%REPEAT\%/s", $contents, $matches);
  $classid = 0;
  switch (substr($_GET["uid"], 0, 4)) {
    case "func": $element = "class"; $classid = str_replace("funclist", "", $_GET["uid"]);
    break;
    case "funh": $element = "hierarchy"; $classid = substr($_GET["uid"], 8, strrpos($_GET["uid"], "h") - 8);
    break;
    case "funa": $element = "acon"; $classid = substr($_GET["uid"], 8, strrpos($_GET["uid"], "ac") - 8);
    break;
  };
  $rep_cont = getFunctional($classid, $matches, $session_id, $element);
  $contents = str_replace($matches[0], $rep_cont, $contents);
  header ($header["xml"]);
  return $contents;
};

// get list of functional relations attributes and return XML contains it
function getfunctionalattrs(){
  global $_GET, $data, $path, $style, $session_id, $language, $header;
  $filename = $path[$style]["tpl"]."/classes.xml";
  $fp = fopen($filename, "r");
  $contents = fread($fp, filesize ($filename));
  fclose ($fp);

  preg_match("/\%REPEAT\%(.*?)\%REPEAT\%/s", $contents, $matches);
  $classid = 0;
  switch (substr($_GET["uid"], 0, 4)) {
    case "func": $element = "class";
      if (substr($_GET["uid"], 4, 1) == "i")
        $fun_id = str_replace("funci", "", $_GET["uid"]);
      else
        $fun_id = str_replace("func", "", $_GET["uid"]);

      // for revers functional constraints
      if (is_numeric(strpos($fun_id, "r"))){
        $fun_id = str_replace("r", "", $fun_id);
        $reverce = 1;
      }else
        $reverce = 0;

      getdata("SELECT f.Func_value as class_id FROM func_constr f WHERE f.id = ".$fun_id." and f.Relation_type = 0", $class_data);
    break;
    case "funh": $element = "hierarchy";
      if (substr($_GET["uid"], 4, 1) == "i")
        $fun_id = str_replace("funhi", "", $_GET["uid"]);
      else
        $fun_id = str_replace("funh", "", $_GET["uid"]);

      // for revers functional constraints
      if (is_numeric(strpos($fun_id, "r"))){
        $fun_id = str_replace("r", "", $fun_id);
        $reverce = 1;
      }else
        $reverce = 0;

      getdata($sql = "SELECT f.Func_value as class_id FROM func_constr f WHERE f.id = ".$fun_id." and f.Relation_type = 1", $class_data);
    break;
    case "funa": $element = "acon";
      if (substr($_GET["uid"], 4, 1) == "i")
        $fun_id = str_replace("funai", "", $_GET["uid"]);
      else
        $fun_id = str_replace("funa", "", $_GET["uid"]);

      // for revers functional constraints
      if (is_numeric(strpos($fun_id, "r"))){
        $fun_id = str_replace("r", "", $fun_id);
        $reverce = 1;
      }else
        $reverce = 0;

      getdata($sql = "SELECT f.Func_value as class_id FROM func_constr f WHERE f.id = ".$fun_id." and f.Relation_type = 2", $class_data);
    break;
  };

  $result = getMultdata($sql = "SELECT c.attr_id as id, t.text FROM class_attr c, attr a, term t WHERE c.class_id = ".$class_data["class_id"]." and a.id = c.attr_id and a.term_id = t.id and a.Type = 1 and t.lang_id = ".$language["content"], $attrs);
  $i = $result;
  //echo $sql;

  while ($class_data["class_id"] > 0){
    getdata("SELECT parent_id as class_id FROM class WHERE id = ".$class_data["class_id"], $class_data);
    $result = getMultdata("SELECT c.attr_id as id, t.text FROM class_attr c, attr a, term t WHERE c.class_id = ".$class_data["class_id"]." and a.id = c.attr_id and a.term_id = t.id and a.Type = 1 and t.lang_id = ".$language["content"], $attrs_temp);
    for ($j = 0; $j < $result; $j++){
      $attrs[$i]["id"] = $attrs_temp[$j]["id"];
      $attrs[$i]["text"] = $attrs_temp[$j]["text"];
      $i++;
    };
  };
  $i_max = count($attrs);
  for ($i = 0; $i < $i_max; $i++){
    if ($reverce == 0)
      $tmp_attr = str_replace("%CLASS_ID%", $_GET["uid"]."a".$attrs[$i]["id"], $matches[1]);
    else
      $tmp_attr = str_replace("%CLASS_ID%", $_GET["uid"]."ar".$attrs[$i]["id"], $matches[1]);
    $tmp_attr = str_replace("%CLASS_NM%", $attrs[$i]["text"], $tmp_attr);
    if (substr($_GET["uid"], 4, 1) == "i")
      $tmp_attr = str_replace("%IMG_TYPE%", "inhattr", $tmp_attr);
    else
      $tmp_attr = str_replace("%IMG_TYPE%", "attr", $tmp_attr);
    if ($reverce == 0)
      $tmp_attr = str_replace("%CLASS_LN%", "index.php?trg=ontoedit&amp;act=functionalattributedata&amp;sid=".$session_id."&amp;uid=".$_GET["uid"]."a".$attrs[$i]["id"], $tmp_attr);
    else
      $tmp_attr = str_replace("%CLASS_LN%", "index.php?trg=ontoedit&amp;act=functionalattributedata&amp;sid=".$session_id."&amp;uid=".$_GET["uid"]."ar".$attrs[$i]["id"], $tmp_attr);
    $tmp_attr = str_replace("%CHILD_LN%", "", $tmp_attr);
    $rep_cont .= $tmp_attr;
  };
  $contents = str_replace($matches[0], $rep_cont, $contents);
  header ($header["xml"]);
  return $contents;

};

function my_func_sort($childs){
  for ($i = 0; $i < count($childs) - 1; $i++){
    for ($j = 0; $j < count($childs) - 1; $j++){
      if (strcmp($childs[$j]["text"], $childs[$j + 1]["text"]) > 0){
        $time = $childs[$j]["text"];
        $childs[$j]["text"] = $childs[$j + 1]["text"];
        $childs[$j + 1]["text"] = $time;

        $time = $childs[$j]["id"];
        $childs[$j]["id"] = $childs[$j + 1]["id"];
        $childs[$j + 1]["id"] = $time;
      };
    };
  };
  return $childs;
};

function get_func_child($parent, $bad_child, &$childs, &$count_childs, $ID){
  $i_max = getMultData("SELECT t.text, c.id FROM class c, term t ".
              "WHERE c.term_id=t.id and c.parent_id=".$parent." and c.id<>".$bad_child, $related_class);
  for ($i = 0; $i < $i_max; $i++){
      $childs[$count_childs]["id"] = $related_class[$i]["id"];
      $childs[$count_childs]["text"] = $related_class[$i]["text"];
      $count_childs++;
    //};
    get_func_child($related_class[$i]["id"], 0, $childs, $count_childs, $ID);
  };
};

function get_func_related_class(&$childs, $ID){
  getData("SELECT parent_id FROM class ".
          "WHERE id=".$ID, $related_class);
  $childs = Array();$count_childs = 0;
  if ($ID != "Thing")
    get_func_child($related_class["parent_id"], $ID, $childs, $count_childs, $ID);
  getData("SELECT t.text FROM class c, term t ".
          "WHERE c.term_id=t.id and c.id=".$related_class["parent_id"], $name_of_class);
  while ($name_of_class["text"] != "Thing"){
    $bad_class = $related_class["parent_id"];
    getData("SELECT c.parent_id, t.text FROM class c, term t ".
            "WHERE c.term_id=t.id and c.id=".$related_class["parent_id"], $related_class);
    get_h_child($related_class["parent_id"], $bad_class, $childs, $count_childs, $ID);
    getData("SELECT t.text FROM class c, term t ".
            "WHERE c.term_id=t.id and c.id=".$related_class["parent_id"], $name_of_class);
  };
  $childs = my_func_sort($childs);
};

// get functional relations data
function functionalData($new_id) {
  global $_GET, $path, $style, $session_id, $data, $term_Thing_ID, $language, $header;
  $filename = $path[$style]["tpl"]."/attrdata.xml";
  $fp = fopen($filename, "r");
  $contents = fread($fp, filesize ($filename));
  fclose ($fp);

  preg_match("/\%REPEAT\%(.*?)\%REPEAT\%/s", $contents, $matches);
  preg_match("/\%REPDAT\%(.*?)\%REPDAT\%/s", $matches[1], $datmatches);
  preg_match("/\%REPOPT\%(.*?)\%REPOPT\%/s", $datmatches[1], $optmatches);
  $rep_cont = "";

  if (substr($_GET["uid"], 4, 1) == "i")
    $FuncID = substr($_GET["uid"], 5);
  else
    $FuncID = substr($_GET["uid"], 4);

  if (is_numeric(strpos($FuncID, "r"))){
    $FuncID = str_replace("r", "", $FuncID);
    $revers = 1;
  }else
    $revers = 0;



  // select relation name
  getData("SELECT t.text FROM term t, func_constr f ".
          "WHERE f.term_id=t.id and f.id=".$FuncID." and t.lang_id = ".$language["content"], $class_name);
  $udata = "";
  if ($data["type"] >= 1) { //user
    //New name
    if ($new_id > -1){
      $contents = str_replace("%NAME%", $class_name["text"], $contents);
      $contents = str_replace("%ID%", $_GET["uid"], $contents);
      $contents = str_replace("%DatHref%", "index.php?trg=ontoedit&amp;act=functionaldata&amp;sid=".$session_id."&amp;uid=".$_GET["uid"], $contents);
      //$contents = str_replace("%Reload%", "reload", $contents);
      //$contents .= getfunctionalattrs();
    };

    switch (substr($_GET["uid"], 0, 4)) {
      case "func":
        getdata("SELECT f.Relation_id as class_id, t.text FROM func_constr f, class c, term t WHERE f.id = ".$FuncID." and f.Relation_type = 0 and f.Relation_id = c.id and c.term_id = t.id and t.lang_id = ".$language["content"], $class_data);
      break;
      case "funh":
        getdata("SELECT h.parent_class_id as class_id, t.text FROM func_constr f, hierarchy h, class c, term t WHERE f.id=".$FuncID." and f.Relation_type = 1 and f.Relation_id = h.id and h.parent_class_id = c.id and c.term_id = t.id and t.lang_id = ".$language["content"], $class_data);
      break;
      case "funa":
        getdata("SELECT a.class1_id as class_id, t.text as text1, t2.text as text2 FROM func_constr f, acon a, class c, term t, class c2, term t2 WHERE f.id=".$FuncID." and f.Relation_type = 2 and f.Relation_id = a.id and a.class1_id = c.id and c.term_id = t.id and t.lang_id = ".$language["content"]." and a.class2_id = c2.id and c2.term_id = t2.id and t2.lang_id = ".$language["content"], $class_data);
        if ($class_data["text"] == "")
          $class_data["text"] = $class_data["text1"].", ".$class_data["text2"];
       break;
    }
    //Class Name
    $classname = str_replace($optmatches[0], "", $datmatches[1]);
    $classname = str_replace("%TYPE%", "Label", $classname);
    $classname = str_replace("%NODE_ID%", "oclassname", $classname);
    $classname = str_replace("%NODE_TL%", getMessage("Class Name"), $classname);
    $classname = str_replace("%VALUE%", $class_data["text"], $classname);

    //Class Name
    $classlb = str_replace($optmatches[0], "", $datmatches[1]);
    $classlb = str_replace("%TYPE%", "Text", $classlb);
    $classlb = str_replace("%NODE_ID%", "ocname", $classlb);
    $classlb = str_replace("%NODE_TL%", getMessage("Functional constraint name"), $classlb);
    $classlb = str_replace("%VALUE%", $class_name["text"], $classlb);
    if ((substr($_GET["uid"], 4, 1) == "i") || ($revers == 1))
      $classlb = str_replace("%ADDITIONAL%", "disabled", $classlb);


    // Functional constraint ID
    $relidlb = str_replace($optmatches[0], "", $datmatches[1]);
    $relidlb = str_replace("%TYPE%", "Hidden", $relidlb);
    $relidlb = str_replace("%NODE_ID%", "ohidd", $relidlb);
    $relidlb = str_replace("%NODE_TL%", "", $relidlb);
    $relidlb = str_replace("%VALUE%", $FuncID, $relidlb);

    $attrs = collect_attributes($class_data["class_id"], 0);
    $result = count($attrs);

    if ( $result > 0){
      getdata("SELECT Sign, AttrOut_id FROM func_constr WHERE id=".$FuncID, $func_sign);
      // generate list of attributes
      $opts = "";
      for ($i = 0; $i < count($attrs); $i++) {
        $opt = str_replace("%OPT_ID%", $attrs[$i]["attr_id"], $optmatches[1]);
        $opt = str_replace("%OPT_TL%", $attrs[$i]["text"], $opt);
        if ($attrs[$i]["attr_id"] == $func_sign["AttrOut_id"])
          $opt = str_replace("%SELECTED%", "selected", $opt);
        else
          $opt = str_replace("%SELECTED%", "0", $opt);
        $opts .= $opt;
      }
      //list of attributes
      $attrsop = str_replace($optmatches[0], $opts, $datmatches[1]);
      $attrsop = str_replace("%TYPE%", "Option", $attrsop);
      $attrsop = str_replace("%NODE_ID%", "oattr", $attrsop);
      $attrsop = str_replace("%NODE_TL%", getMessage("Output attribute"), $attrsop);
      if ((substr($_GET["uid"], 4, 1) == "i") || ($revers == 1))
        $attrsop = str_replace("%ADDITIONAL%", "disabled", $attrsop);

      // generate list of signs
      $opts = "";
      $opt = str_replace("%OPT_ID%", 0, $optmatches[1]);
      $opt = str_replace("%OPT_TL%", "=", $opt);
      if ($func_sign["Sign"] == 0)
        $opt = str_replace("%SELECTED%", "selected", $opt);
      else
        $opt = str_replace("%SELECTED%", "0", $opt);
      $opts .= $opt;
      $opt = str_replace("%OPT_ID%", 1, $optmatches[1]);
      $opt = str_replace("%OPT_TL%", "&gt;", $opt);
      if ($func_sign["Sign"] == 1)
        $opt = str_replace("%SELECTED%", "selected", $opt);
      else
        $opt = str_replace("%SELECTED%", "0", $opt);
      $opts .= $opt;
      $opt = str_replace("%OPT_ID%", 2, $optmatches[1]);
      $opt = str_replace("%OPT_TL%", "&lt;", $opt);
      if ($func_sign["Sign"] == 2)
        $opt = str_replace("%SELECTED%", "selected", $opt);
      else
        $opt = str_replace("%SELECTED%", "0", $opt);
      $opts .= $opt;
      //list of signs
      $signop = str_replace($optmatches[0], $opts, $datmatches[1]);
      $signop = str_replace("%TYPE%", "Option", $signop);
      $signop = str_replace("%NODE_ID%", "osign", $signop);
      $signop = str_replace("%NODE_TL%", getMessage("Sign"), $signop);
      if ((substr($_GET["uid"], 4, 1) == "i") || ($revers == 1))
        $signop = str_replace("%ADDITIONAL%", "disabled", $signop);

      getdata("SELECT f.Func_type, f.Func_value FROM func_constr f WHERE f.id=".$FuncID." and f.Func_type = 1 UNION SELECT f.Func_type, c.id FROM func_constr f, class c WHERE f.id=".$FuncID." and f.Func_type = 0 and f.Func_value = c.id", $func_value);
      if ($func_value["Func_type"] == 1){
        $func_constant = $func_value["Func_value"];
        $func_method = 0;
      }else{
        $func_constant = "";
        $func_method = $func_value["Func_value"];
      };
      // Function value constant
      $constantlb = str_replace($optmatches[0], "", $datmatches[1]);
      $constantlb = str_replace("%TYPE%", "Text", $constantlb);
      $constantlb = str_replace("%NODE_ID%", "oconstant", $constantlb);
      $constantlb = str_replace("%NODE_TL%", getMessage("Function value constant"), $constantlb);
      $constantlb = str_replace("%VALUE%", $func_constant, $constantlb);
      if ((substr($_GET["uid"], 4, 1) == "i") || ($revers == 1))
        $constantlb = str_replace("%ADDITIONAL%", "disabled", $constantlb);

      //Function value method
      switch (substr($_GET["uid"], 0, 4)) {
        case "func":
          getMultdata($sql = "SELECT ctmo.id, t.text FROM func_constr f, class c, class ctmo, term t WHERE f.Relation_type = 0 and f.Relation_id = c.id and ctmo.onto_id = c.onto_id and ctmo.base_onto_id <> c.base_onto_id and ctmo.base_onto_id <> 0 and ctmo.term_id = t.id and f.id = ".$FuncID." and t.lang_id = ".$language["content"]." ORDER BY t.text", $func_methods);
        break;
        case "funh":
          getMultdata($sql = "SELECT ctmo.id, t.text FROM func_constr f, class c, class ctmo, term t, hierarchy h WHERE f.Relation_type = 1 and f.Relation_id = h.id and h.parent_class_id = c.id and ctmo.onto_id = c.onto_id and ctmo.base_onto_id <> c.base_onto_id and ctmo.base_onto_id <> 0 and ctmo.term_id = t.id and f.id = ".$FuncID." and t.lang_id = ".$language["content"]." ORDER BY t.text", $func_methods);
        break;
        case "funa":
          getMultdata($sql = "SELECT ctmo.id, t.text FROM func_constr f, class c, class ctmo, term t, acon h WHERE f.Relation_type = 2 and f.Relation_id = h.id and h.class1_id = c.id and ctmo.onto_id = c.onto_id and ctmo.base_onto_id <> c.base_onto_id and ctmo.base_onto_id <> 0 and ctmo.term_id = t.id and f.id = ".$FuncID." and t.lang_id = ".$language["content"]." ORDER BY t.text", $func_methods);
        break;
      }

      $opts = "";
        $opt = str_replace("%OPT_ID%", 0, $optmatches[1]);
        $opt = str_replace("%OPT_TL%", "---".getMessage("Function value constant")."---", $opt);
        $opt = str_replace("%SELECTED%", "0", $opt);
        $opts .= $opt;
      for ($i = 0; $i < count($func_methods); $i++) {
        $opt = str_replace("%OPT_ID%", $func_methods[$i]["id"], $optmatches[1]);
        $opt = str_replace("%OPT_TL%", $func_methods[$i]["text"], $opt);
        if ($func_methods[$i]["id"] == $func_method)
          $opt = str_replace("%SELECTED%", "selected", $opt);
        else
          $opt = str_replace("%SELECTED%", "0", $opt);
        $opts .= $opt;
      }
      //list of methods
      $funcmethodop = str_replace($optmatches[0], $opts, $datmatches[1]);
      $funcmethodop = str_replace("%TYPE%", "Option", $funcmethodop);
      $funcmethodop = str_replace("%NODE_ID%", "omethod", $funcmethodop);
      $funcmethodop = str_replace("%NODE_TL%", getMessage("Function value method"), $funcmethodop);
      if ((substr($_GET["uid"], 4, 1) == "i") || ($revers == 1))
        $funcmethodop = str_replace("%ADDITIONAL%", "disabled", $funcmethodop);

      // buttons save
      $ubutn = str_replace($optmatches[0], "", $datmatches[1]);
      $ubutn = str_replace("%TYPE%", "Button", $ubutn);
      $ubutn = str_replace("%NODE_ID%", "obutn", $ubutn);
      $ubutn = str_replace("%NODE_TL%", getMessage("Save"), $ubutn);
      $ubutn = str_replace("%VALUE%", "'0','ocname','ohidd', 'oattr', 'osign', 'oconstant', 'omethod'", $ubutn);
      if ((substr($_GET["uid"], 4, 1) == "i") || ($revers == 1))
        $ubutn = str_replace("%ADDITIONAL%", "disabled", $ubutn);

    };

    $udata = str_replace($datmatches[0], $classname.$classlb.$iclasslb.$attrsop.$signop.$constantlb.$funcmethodop.$ubutn.$relidlb, $matches[1]);
    $udata = str_replace("%GROUP_ID%", "0", $udata);
    if ($revers ==0)
      $udata = str_replace("%GROUP_TL%", getMessage("Functional constraints"), $udata);
    else
      $udata = str_replace("%GROUP_TL%", getMessage("Reverse Functional constraints"), $udata);

    //Action: return to the ontologies
    $btn1 = str_replace($optmatches[0], "", $datmatches[1]);
    $btn1 = str_replace("%TYPE%", "Button", $btn1);
    $btn1 = str_replace("%NODE_ID%", "", $btn1);
    $btn1 = str_replace("%NODE_TL%", getMessage("Ontologies"), $btn1);
    $btn1 = str_replace("%VALUE%", "'wd_tree', 'index.php?trg=ontoedit&amp;sid=".
      $session_id."&amp;act=ontolist&amp;sel=".$onto_name["id"]."'", $btn1);

    $btns = str_replace($datmatches[0], $btn1, $matches[1]);
    $btns = str_replace("%GROUP_ID%", "1", $btns);
    $btns = str_replace("%GROUP_TL%", getMessage("Action"), $btns);
  }
  header ($header["xml"]);
  return str_replace($matches[0], $udata.$btns, $contents);
}

// get attribute data
function functionalattributeData() {
  global $_GET, $path, $style, $session_id, $data, $term_Thing_ID, $language, $header;
  $filename = $path[$style]["tpl"]."/attrdata.xml";
  $fp = fopen($filename, "r");
  $contents = fread($fp, filesize ($filename));
  fclose ($fp);

  preg_match("/\%REPEAT\%(.*?)\%REPEAT\%/s", $contents, $matches);
  preg_match("/\%REPDAT\%(.*?)\%REPDAT\%/s", $matches[1], $datmatches);
  preg_match("/\%REPOPT\%(.*?)\%REPOPT\%/s", $datmatches[1], $optmatches);
  $rep_cont = "";

  if ($FuncID = -1){
    if (substr($_GET["uid"], 4, 1) == "i")
      $FuncID = substr($_GET["uid"], 5, strrpos($_GET["uid"], "a") - 5);
    else
      $FuncID = substr($_GET["uid"], 4, strrpos($_GET["uid"], "a") - 4);

    $AttrID = substr($_GET["uid"], strrpos($_GET["uid"], "a") + 1);
  };

  // for revers functional constraints
  if (is_numeric(strpos($FuncID, "r"))){
    $FuncID = str_replace("r", "", $FuncID);
    $reverce = 1;
  }else
    $reverce = 0;

  if (is_numeric(strpos($AttrID, "r")))
    $AttrID = str_replace("r", "", $AttrID);


  $udata = "";
  if ($data["type"] >= 1) { //user
    // select attribute name
    getData("SELECT t.text FROM term t, attr a WHERE a.term_id=t.id and a.id=".$AttrID, $class_name);
    //Attribute name
    $classlb = str_replace($optmatches[0], "", $datmatches[1]);
    $classlb = str_replace("%TYPE%", "Label", $classlb);
    $classlb = str_replace("%NODE_TL%", getMessage("Attributes Name"), $classlb);
    $classlb = str_replace("%VALUE%", $class_name["text"], $classlb);
    // Functional constraint ID
    $relidlb = str_replace($optmatches[0], "", $datmatches[1]);
    $relidlb = str_replace("%TYPE%", "Hidden", $relidlb);
    $relidlb = str_replace("%NODE_ID%", "ohidd", $relidlb);
    $relidlb = str_replace("%NODE_TL%", "", $relidlb);
    $relidlb = str_replace("%VALUE%", $FuncID, $relidlb);
    // Attribute ID
    $attridlb = str_replace($optmatches[0], "", $datmatches[1]);
    $attridlb = str_replace("%TYPE%", "Hidden", $attridlb);
    $attridlb = str_replace("%NODE_ID%", "ohidd2", $attridlb);
    $attridlb = str_replace("%NODE_TL%", "", $attridlb);
    $attridlb = str_replace("%VALUE%", $AttrID, $attridlb);

    switch (substr($_GET["uid"], 0, 4)) {
      case "func":
        getdata("SELECT f.Relation_id as class_id, f.attrOut_id FROM func_constr f WHERE f.id = ".$FuncID." and f.Relation_type = 0", $class_data);
      break;
      case "funh":
        getdata("SELECT h.parent_class_id as class_id, f.attrOut_id FROM func_constr f, hierarchy h WHERE f.id=".$FuncID." and f.Relation_type = 1 and f.Relation_id = h.id", $class_data);
      break;
      case "funa":
        getdata("SELECT a.class1_id as class_id, f.attrOut_id FROM func_constr f, acon a WHERE f.id=".$FuncID." and f.Relation_type = 2 and f.Relation_id = a.id", $class_data);
      break;
    }
    $attrs = collect_attributes($class_data["class_id"], $class_data["attrOut_id"]);
    $result = count($attrs);


    if ( $result > 0){
      getdata("SELECT AttrID FROM func_attrs WHERE FuncConstrID = ".$FuncID." and IPID = ".$AttrID, $func_attr);
      // generate list of attributes
      $opts = "";
      $opt = str_replace("%OPT_ID%", 0, $optmatches[1]);
      $opt = str_replace("%OPT_TL%", " ", $opt);
      $opts .= $opt;
      for ($i = 0; $i < count($attrs); $i++) {
        $opt = str_replace("%OPT_ID%", $attrs[$i]["attr_id"], $optmatches[1]);
        $opt = str_replace("%OPT_TL%", $attrs[$i]["text"], $opt);
        if ($attrs[$i]["attr_id"] == $func_attr["AttrID"])
          $opt = str_replace("%SELECTED%", "selected", $opt);
        else
          $opt = str_replace("%SELECTED%", "0", $opt);
        $opts .= $opt;
      }
      //list of attributes
      $attrsop = str_replace($optmatches[0], $opts, $datmatches[1]);
      $attrsop = str_replace("%TYPE%", "Option", $attrsop);
      $attrsop = str_replace("%NODE_ID%", "oattr", $attrsop);
      $attrsop = str_replace("%NODE_TL%", getMessage("Corresponded attribute"), $attrsop);
      if (substr($_GET["uid"], 4, 1) == "i" || $reverce == 1)
        $attrsop = str_replace("%ADDITIONAL%", "disabled", $attrsop);

      // buttons save
      $ubutn = str_replace($optmatches[0], "", $datmatches[1]);
      $ubutn = str_replace("%TYPE%", "Button", $ubutn);
      $ubutn = str_replace("%NODE_ID%", "obutn", $ubutn);
      $ubutn = str_replace("%NODE_TL%", getMessage("Save"), $ubutn);
      $ubutn = str_replace("%VALUE%", "'0', 'ohidd', 'ohidd2', 'oattr'", $ubutn);
      if (substr($_GET["uid"], 4, 1) == "i" || $reverce == 1)
        $ubutn = str_replace("%ADDITIONAL%", "disabled", $ubutn);
    };

    $udata = str_replace($datmatches[0], $classlb.$attrsop.$ubutn.$relidlb.$attridlb, $matches[1]);
    $udata = str_replace("%GROUP_ID%", "0", $udata);
    $udata = str_replace("%GROUP_TL%", getMessage("Corresponded attribute"), $udata);

    //Action: return to the ontologies
    $btn1 = str_replace($optmatches[0], "", $datmatches[1]);
    $btn1 = str_replace("%TYPE%", "Button", $btn1);
    $btn1 = str_replace("%NODE_ID%", "", $btn1);
    $btn1 = str_replace("%NODE_TL%", getMessage("Ontologies"), $btn1);
    $btn1 = str_replace("%VALUE%", "'wd_tree', 'index.php?trg=ontoedit&amp;sid=".
      $session_id."&amp;act=ontolist&amp;sel=".$onto_name["id"]."'", $btn1);

    $btns = str_replace($datmatches[0], $btn1, $matches[1]);
    $btns = str_replace("%GROUP_ID%", "1", $btns);
    $btns = str_replace("%GROUP_TL%", getMessage("Action"), $btns);
  }
  header ($header["xml"]);
  return str_replace($matches[0], $udata.$btns, $contents);
}

// create new functional constraint
function createFunctional() {
  global $_GET, $data, $path, $style, $session_id, $language, $header;
  switch (substr($_GET["uid"], 0, 4)) {
    case "func":
      $Relation_Type = 0;
      $Relation_Name = "funclist";
      $element_id = substr($_GET["uid"], 8);
      $parent_id = $Relation_Name.$element_id;
      $xmlsrc = $Relation_Name.$element_id;
    break;
    case "funh":
      $Relation_Type = 1;
      $Relation_Name = "funhlist";
      getdata("SELECT id FROM hierarchy WHERE parent_class_id = ".substr($_GET["uid"], 8, strrpos(substr($_GET["uid"], 8), "h"))." and child_class_id = ".substr(substr($_GET["uid"], 8), strrpos(substr($_GET["uid"], 8), "h") + 1), $data_hierarchy);
      $element_id = $data_hierarchy["id"];
      $parent_id = $Relation_Name.substr($_GET["uid"], 8, strrpos(substr($_GET["uid"], 8), "h"))."h".substr(substr($_GET["uid"], 8), strrpos(substr($_GET["uid"], 8), "h") + 1);
      $xmlsrc = $Relation_Name.substr($_GET["uid"], 8, strrpos(substr($_GET["uid"], 8), "h"))."h".substr(substr($_GET["uid"], 8), strrpos(substr($_GET["uid"], 8), "h") + 1);
    break;
    case "funa":
      $Relation_Type = 2;
      $Relation_Name = "funalist";
      getdata($sql = "SELECT id FROM acon WHERE class1_id = ".substr($_GET["uid"], 8, strrpos(substr($_GET["uid"], 8), "ac"))." and class2_id = ".substr(substr($_GET["uid"], 8), strrpos(substr($_GET["uid"], 8), "ac") + 2), $data_acon);
      $element_id = $data_acon["id"];
      $parent_id = $Relation_Name.substr($_GET["uid"], 8, strrpos(substr($_GET["uid"], 8), "ac"))."ac".substr(substr($_GET["uid"], 8), strrpos(substr($_GET["uid"], 8), "ac") + 2);
      $xmlsrc = $Relation_Name.substr($_GET["uid"], 8, strrpos(substr($_GET["uid"], 8), "ac"))."ac".substr(substr($_GET["uid"], 8), strrpos(substr($_GET["uid"], 8), "ac") + 2);
    break;
  }

  $prev_id = 0;
  $filename = $path[$style]["tpl"]."/action.xml";
  $fp = fopen($filename, "r");
  $contents = fread($fp, filesize ($filename));
  fclose ($fp);
  preg_match("/\%REPEAT\%(.*?)\%REPEAT\%/s", $contents, $matches);
  if ($data["type"] >= 1) { //user
    // if user have a rights for adding
    if (getdata("SELECT id FROM func_constr WHERE AttrOut_id is null and Relation_Type = ".$Relation_Type." and Relation_id = ".$element_id, $data) != 1){
      insertRecord($SQL = "INSERT INTO term (lang_id, text) VALUES(".$language["content"].", 'Functional constraint');");
      $prev_id = GetPreviousInsertedID();
      insertRecord("INSERT INTO func_constr (term_id, Relation_type, Relation_id) VALUES(".$prev_id.", ".$Relation_Type.", ".$element_id.");");
      if ($prev_id = GetPreviousInsertedID() > 0){
        $contents = str_replace("%SCCSS%", "1", $contents);
        $childs[0]["id"] = -1;
      } else {
        $childs[0]["id"] = "0";
        $contents = str_replace("%SCCSS%", "0", $contents);
        $datatmp["id"] = 0;
      };
    } else {
      $childs[0]["id"] = "0";
      $contents = str_replace("%SCCSS%", "0", $contents);
      $datatmp["id"] = 0;
    };
  } else {
    $childs[0]["id"] = "0";
    $contents = str_replace("%SCCSS%", "0", $contents);
    $datatmp["id"] = 0;
  }
  $tmp_cont = str_replace("%NODE_ID%", $Relation_Name.$Relation_Type, $matches[1]);
  $tmp_cont = str_replace("%NODE_NM%", getMessage("Name"), $tmp_cont);
  $tmp_cont = str_replace("%IMG_TYPE%", "class", $tmp_cont);
  $tmp_cont = str_replace("%NODE_LN%", "index.php?trg=ontoedit&amp;act=functionaldata&amp;sid=".$session_id."&amp;uid=".$Relation_Name.$Relation_Type, $tmp_cont);
  $contents = str_replace($matches[0], $tmp_cont, $contents);
  $contents = str_replace("%XMLSRC%", "index.php?trg=ontoedit&amp;act=functionallist&amp;sid=".$session_id."&amp;uid=".$xmlsrc."&amp;sel=".$Relation_Name.$Relation_Type, $contents);
  $contents = str_replace("%ACT_ID%", "Add", $contents);
  $contents = str_replace("%PARENT%", $parent_id, $contents);

  header ($header["xml"]);
  return $contents;
}

function deletefunctional() {
  global $_GET, $data, $path, $style, $session_id, $header;
  $filename = $path[$style]["tpl"]."/action.xml";
  $fp = fopen($filename, "r");
  $contents = fread($fp, filesize ($filename));
  fclose ($fp);

  preg_match("/\%REPEAT\%(.*?)\%REPEAT\%/s", $contents, $matches);
  switch (substr($_GET["uid"], 0, 4)) {
    case "func":
      $sql_str = "SELECT Relation_id FROM func_constr f WHERE id = ".substr($_GET["uid"], 4);
      getData($sql_str, $parent_id);
      if ($parent_id["Relation_id"] <> "")
        $select = "funclist".$parent_id["Relation_id"];
      else
        $select = "";
      break;
    case "funh":
      $sql_str = "SELECT h.parent_class_id, h.child_class_id FROM func_constr f, hierarchy h WHERE f.id = ".substr($_GET["uid"], 4)." and f.Relation_id = h.id";
      getData($sql_str, $parent_id);
      if ($parent_id["parent_class_id"] <> "" && $parent_id["child_class_id"] <> "")
        $select = "funhlist".$parent_id["parent_class_id"]."h".$parent_id["child_class_id"];
      else
        $select = "";
      break;
    case "funa":
      $sql_str = "SELECT h.class1_id, h.class2_id FROM func_constr f, acon h WHERE f.id = ".substr($_GET["uid"], 4)." and f.Relation_id = h.id";
      getData($sql_str, $parent_id);
      if ($parent_id["class1_id"] <> "" && $parent_id["class2_id"] <> "")
        $select = "funalist".$parent_id["class1_id"]."ac".$parent_id["class2_id"];
      else
        $select = "";
      break;
  }
  if ($select <> ""){
    //Delete functional constraint
    insertRecord("DELETE FROM func_constr WHERE id=".substr($_GET["uid"], 4));
    $contents = str_replace("%SCCSS%", "1", $contents);

    $contents = str_replace($matches[0], "", $contents);
    $contents = str_replace("%ACT_ID%", "Delete", $contents);
    $contents = str_replace("%PARENT%", $_GET["uid"], $contents);
    //echo $sql_str.substr($_GET["uid"], 0, 4).$parent_id["Relation_id"];
    $contents = str_replace("%SELECT%", $select, $contents);
  }else{
    $contents = str_replace("%SCCSS%", "0", $contents);
  };
  header ($header["xml"]);
  return $contents;
}

function updatefunctional() {
  //echo "'0','ocname','ohidd', 'oattr', 'osign', 'oconstant', 'omethod'";
  global $_GET, $data, $path, $style, $session_id, $term_Thing_ID, $language, $header;
  $comment = "";
  $_GET["ocname"] = utf8Encode($_GET["ocname"]);
  $_GET["ohidd"] = utf8Encode($_GET["ohidd"]);
  $_GET["oattr"] = utf8Encode($_GET["oattr"]);
  $_GET["osign"] = utf8Encode($_GET["osign"]);
  $_GET["oconstant"] = utf8Encode($_GET["oconstant"]);
  $_GET["omethod"] = utf8Encode($_GET["omethod"]);

  //update class_name
  if ($_GET["ocname"] <> ""){
    $sql_str = "UPDATE func_constr f, term t SET t.text = '".$_GET["ocname"]."' WHERE f.term_id = t.id and f.id=".$_GET["ohidd"];
    insertRecord($sql_str);
  };

  // update output_attr, sign, function_value_constant, function_value_method
  $run = 0;
  if ($_GET["omethod"] == 0){
    if ($_GET["oconstant"] <> ""){
      $func_value = $_GET["oconstant"];
      $func_type = 1;
      if (is_numeric($func_value)){
        $run = 1;
      };
    };
  }else{
    $func_value = $_GET["omethod"];
    $func_type = 0;
    $run = 1;
  };
  if ($run == 1){
    $sql_str = "UPDATE func_constr SET AttrOut_id = ".$_GET["oattr"].", Sign = ".$_GET["osign"].", Func_type = ".$func_type." ,Func_value = ".$func_value." WHERE id=".$_GET["ohidd"];
    insertRecord($sql_str);
  };
  header ($header["xml"]);
  //$contents = FunctionalData(0);

  //update tree (adding attributes)
  $filename = $path[$style]["tpl"]."/action.xml";
  $fp = fopen($filename, "r");
  $contents = fread($fp, filesize ($filename));
  fclose ($fp);
  preg_match("/\%REPEAT\%(.*?)\%REPEAT\%/s", $contents, $matches);


  $contents = str_replace("%SCCSS%", "1", $contents);
  $contents = str_replace($matches[0], "", $contents);
  $contents = str_replace("%XMLSRC%", "index.php?trg=ontoedit&amp;act=getfunctionalattrs&amp;sid=".$session_id."&amp;uid=".$_GET["uid"]."&amp;sel=func0", $contents);
  $contents = str_replace("%NAME%", $_GET["ocname"], $contents);
  $contents = str_replace("%SELECT%", $_GET["uid"], $contents);
  $contents = str_replace("%ACT_ID%", "Add", $contents);
  $contents = str_replace("%PARENT%", $_GET["uid"], $contents);

  return $contents;
}

function updatefunctionalattr() {
  global $_GET, $data, $path, $style, $session_id, $term_Thing_ID, $language, $header;
  $comment = "";
  $_GET["ohidd"] = utf8Encode($_GET["ohidd"]);
  $_GET["ohidd2"] = utf8Encode($_GET["ohidd2"]);
  $_GET["oattr"] = utf8Encode($_GET["oattr"]);
  $sql_str = "SELECT id FROM Func_Attrs WHERE FuncConstrID = ".$_GET["ohidd"]." and IPID = ".$_GET["ohidd2"];
  if (GetData($sql_str, $func_attr_id) == 1){
    // update corresponded_attr
    $sql_str = "UPDATE Func_Attrs SET AttrID = ".$_GET["oattr"]." WHERE IPID = ".$_GET["ohidd2"]." and FuncConstrID = ".$_GET["ohidd"];
    insertRecord($sql_str);
  }else{
    // insert corresponded_attr
    $sql_str = "INSERT INTO Func_Attrs (FuncConstrID, AttrID, IPID) VALUES (".$_GET["ohidd"].", ".$_GET["oattr"].", ".$_GET["ohidd2"].")";
    insertRecord($sql_str);
  };
  header ($header["xml"]);
  $contents = FunctionalAttributeData(-1, -1);
  return $contents;
}
?>